﻿using Microsoft.EntityFrameworkCore;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json;
using ST.Common.Data;
using ST.Common.Util;
using ST.Common.Util.Model;
using ST.Common.Util.Mvc;
using ST.Buz.Base;
using ST.Buz.Base.Entity;
using System;
using System.Collections.Generic;
using System.Linq;
using Microsoft.AspNetCore.Mvc.Rendering;
using ST.Buz.Base.ViewModel;
using Microsoft.Data.SqlClient;

namespace ST.Buz.Service
{
	public partial interface IServiceSysLog
	{
		/// <summary>
		/// 新增日志
		/// </summary>
		/// <param name="sessionCurrent"></param>
		/// <param name="dt"></param>
		/// <param name="content"></param>
		/// <returns></returns>
		int Add(UserSession sessionCurrent, string ip, string content, DateTime? dt = null);

		/// <summary>
		/// 
		/// </summary>
		/// <param name="sessionCurrent"></param>
		/// <param name="title"></param>
		/// <param name="obj"></param>
		/// <param name="dt"></param>
		/// <returns></returns>
		int Add(UserSession sessionCurrent, string ip, string title, object obj, DateTime? dt = null);

		/// <summary>
		/// 获取分页列表
		/// </summary>
		PageData GetPageList(VMS_Sys_Log searchModel);

		/// <summary>
		/// 删除日志
		/// </summary>
		/// <param name="id"></param>
		/// <param name="sessionCurrent"></param>
		/// <returns></returns>
		bool Delete(int id, UserSession sessionCurrent);

		/// <summary>
		/// 批量删除日志
		/// </summary>
		/// <returns></returns>
		bool BatchDelete(int[] ids, UserSession sessionCurrent);

		/// <summary>
		/// 清空日志
		/// </summary>
		/// <param name="sessionCurrent"></param>
		/// <returns></returns>
		bool Clear(UserSession sessionCurrent);

		/// <summary>
		/// 根据id获取详细信息
		/// </summary>
		/// <param name="id"></param>
		/// <returns></returns>
		Sys_Log GetViewDetail(int id, UserSession sessionCurrent);
	}

	public partial class ServiceSysLog
	{
		public ServiceSysLog(BuzContext ctx,
			ILogger<ServiceSysLog> log)
		{
			context = ctx;
			logger = log;
		}

		public int Add(UserSession sessionCurrent, string ip, string content, DateTime? dt = null)
		{
			if (string.IsNullOrEmpty(ip))
			{
				ip = GetRequestIP();
			}
			Sys_Log log = new Sys_Log();
			log.LogLevel = (int)LogLevel.Information;
			log.LogManID = sessionCurrent.UserID;
			log.LogManName = sessionCurrent.UserName;
			log.LogManIP = ip;
			log.LogTime = dt == null ? DateTime.Now : dt.Value;
			log.LogContent = content;
			log.OrgID = sessionCurrent.OrgID;
			return Add(log);
		}

		public int Add(UserSession sessionCurrent, string ip, string title, object obj, DateTime? dt = null)
		{
			if (string.IsNullOrEmpty(ip))
			{
				ip = GetRequestIP();
			}
			Sys_Log log = new Sys_Log();
			log.LogLevel = (int)LogLevel.Information;
			log.LogManID = sessionCurrent.UserID;
			log.LogManName = sessionCurrent.UserName;
			log.LogManIP = ip;
			log.LogTime = dt == null ? DateTime.Now : dt.Value;
			log.LogContent = title + Newtonsoft.Json.JsonConvert.SerializeObject(obj, new JsonSerializerSettings()
			{
				NullValueHandling = NullValueHandling.Ignore
			});
			log.OrgID = sessionCurrent.OrgID;
			return Add(log);
		}

		/// <summary>
		/// 根据id获取详细信息
		/// </summary>
		/// <param name="id"></param>
		/// <returns></returns>
		public Sys_Log GetViewDetail(int id, UserSession sessionCurrent)
		{
			try
			{
				var model = context.SysLog.SingleOrDefault(m => m.ID == id);
				if (model != null)
				{
					throw new ArgumentException("未找到相关信息");
				}
				return model;
			}
			catch (ArgumentException ex)
			{
				throw ex;
			}
			catch (Exception ex)
			{
				logger.LogError(ex.InnerException ?? ex, "获取对象信息出错");
				throw new BuzException("获取对象信息失败，" + (ex.InnerException != null ? ex.InnerException.Message : ex.Message));
			}
		}

		/// <summary>
		/// 删除具体操作
		/// </summary>
		/// <param name="id"></param>
		/// <param name="ip"></param>
		/// <param name="dtNow"></param>
		/// <param name="sessionCurrent"></param>
		protected void DeleteWithinTrans(int id)
		{
			SqlParameter[] paras = new SqlParameter[]{
				new SqlParameter("@ID",id)
			};
			context.Database.ExecuteSqlRaw("DELETE FROM Sys_Log WHERE ID=@ID", paras);
		}

		/// <summary>
		/// 删除日志
		/// </summary>
		/// <param name="id"></param>
		/// <param name="sessionCurrent"></param>
		/// <returns></returns>
		public bool Delete(int id, UserSession sessionCurrent)
		{
			bool success = false;
			try
			{
				//if (logger.IsEnabled(LogLevel.Debug))
				//{
				//	logger.LogDebug($"参数->id:{id}，state:{state}，remark:{remark}");
				//}
				if (sessionCurrent == null)
				{
					throw new BuzException("用户会话不能为空");
				}

				using (var trans = context.Database.BeginTransaction())
				{
					try
					{
						#region 事务具体操作
						DeleteWithinTrans(id);
						#endregion

						trans.Commit();
					}
					catch (Exception ex)
					{
						trans.Rollback();
						throw ex.InnerException ?? ex;
					}
				}

				success = true;
			}
			catch (BuzException ex)
			{
				throw ex;
			}
			catch (Exception ex)
			{
				logger.LogError(ex.InnerException ?? ex, "删除系统日志出错");
				throw new BuzException("删除系统日志失败，" + (ex.InnerException != null ? ex.InnerException.Message : ex.Message));
			}
			return success;
		}

		/// <summary>
		/// 批量删除日志
		/// </summary>
		/// <returns></returns>
		public bool BatchDelete(int[] ids, UserSession sessionCurrent)
		{
			bool success = false;
			try
			{
				//if (logger.IsEnabled(LogLevel.Debug))
				//{
				//	logger.LogDebug($"参数->id:{id}，state:{state}，remark:{remark}");
				//}
				if (sessionCurrent == null)
				{
					throw new BuzException("用户会话不能为空");
				}

				if (ids == null || ids.Length == 0)
				{
					throw new BuzException("参数不能为空");
				}

				using (var trans = context.Database.BeginTransaction())
				{
					try
					{
						#region 事务具体操作
						foreach (int id in ids)
						{
							DeleteWithinTrans(id);
						}
						#endregion

						trans.Commit();
					}
					catch (Exception ex)
					{
						trans.Rollback();
						throw ex.InnerException ?? ex;
					}
				}

				success = true;
			}
			catch (BuzException ex)
			{
				throw ex;
			}
			catch (Exception ex)
			{
				logger.LogError(ex.InnerException ?? ex, "批量删除日志出错");
				throw new BuzException("批量删除日志失败，" + (ex.InnerException != null ? ex.InnerException.Message : ex.Message));
			}
			return success;
		}

		/// <summary>
		/// 清空日志
		/// </summary>
		/// <param name="sessionCurrent"></param>
		/// <returns></returns>
		public bool Clear(UserSession sessionCurrent)
		{
			bool success = false;
			try
			{
				//if (logger.IsEnabled(LogLevel.Debug))
				//{
				//	logger.LogDebug($"参数->id:{id}，state:{state}，remark:{remark}");
				//}
				if (sessionCurrent == null)
				{
					throw new BuzException("用户会话不能为空");
				}

				using (var trans = context.Database.BeginTransaction())
				{
					try
					{
						#region 事务具体操作
						context.Database.ExecuteSqlRaw("DELETE FROM Sys_Log WHERE OrgID={0}", sessionCurrent.OrgID);
						#endregion

						trans.Commit();
					}
					catch (Exception ex)
					{
						trans.Rollback();
						throw ex.InnerException ?? ex;
					}
				}

				success = true;
			}
			catch (BuzException ex)
			{
				throw ex;
			}
			catch (Exception ex)
			{
				logger.LogError(ex.InnerException ?? ex, "清空系统日志出错");
				throw new BuzException("清空系统日志失败，" + (ex.InnerException != null ? ex.InnerException.Message : ex.Message));
			}
			return success;
		}

		/// <summary>
		/// 分页列表
		/// </summary>
		public PageData GetPageList(VMS_Sys_Log searchModel)
		{
			PageData result = null;
			try
			{
				searchModel.Validate();

				var query = (from log in context.SysLog
							 select log).AsNoTracking();
				if (!string.IsNullOrEmpty(searchModel.content))
				{
					query = query.Where(m => EF.Functions.Like(m.LogContent, "%" + searchModel.content + "%"));
				}
				if (!string.IsNullOrEmpty(searchModel.srcurl))
				{
					query = query.Where(m => m.SrcUrl == searchModel.srcurl);
				}
				if (!string.IsNullOrEmpty(searchModel.logman))
				{
					query = query.Where(m => m.LogManName == searchModel.logman);
				}
				if (!string.IsNullOrEmpty(searchModel.logmanip))
				{
					query = query.Where(m => m.LogManIP == searchModel.logmanip);
				}
				if (searchModel.logmanid.HasValue)
				{
					query = query.Where(m => m.LogManID == searchModel.logmanid.Value);
				}
				if (searchModel.moduleid.HasValue)
				{
					query = query.Where(m => m.ModuleID == searchModel.moduleid.Value);
				}
				if (!string.IsNullOrEmpty(searchModel.modulename))
				{
					query = query.Where(m => m.ModuleName == searchModel.modulename);
				}
				if (!string.IsNullOrEmpty(searchModel.modulecode))
				{
					query = query.Where(m => m.ModuleCode == searchModel.modulecode);
				}
				if (searchModel.serviceid.HasValue)
				{
					query = query.Where(m => m.ServiceID == searchModel.serviceid.Value);
				}
				if (!string.IsNullOrEmpty(searchModel.servicename))
				{
					query = query.Where(m => m.ServiceName == searchModel.servicename);
				}
				if (!string.IsNullOrEmpty(searchModel.servicecode))
				{
					query = query.Where(m => m.ServiceCode == searchModel.servicecode);
				}
				if (searchModel.actionid.HasValue)
				{
					query = query.Where(m => m.ActionID == searchModel.actionid.Value);
				}
				if (!string.IsNullOrEmpty(searchModel.actionname))
				{
					query = query.Where(m => m.ActionName == searchModel.actionname);
				}
				if (!string.IsNullOrEmpty(searchModel.actioncode))
				{
					query = query.Where(m => m.ActionCode == searchModel.actioncode);
				}
				if (DateTime.MinValue != searchModel.date_s)
				{
					query = query.Where(m => m.LogTime >= searchModel.date_s);
				}
				if (DateTime.MinValue != searchModel.date_e)
				{
					query = query.Where(m => m.LogTime <= searchModel.date_e);
				}

				switch (searchModel.sortby)
				{
					default:
						query = searchModel.orderby == Common.Util.Mvc.SortOrder.Ascending ? query.OrderBy(e => e.ID) : query.OrderByDescending(e => e.ID);
						break;
				}
				result = new PageData(searchModel.pnum.Value, searchModel.psize.Value);
				result.Load(query);
			}
			catch (BuzException ex)
			{
				throw ex;
			}
			catch (Exception ex)
			{
				logger.LogError(ex.InnerException ?? ex, "获取分页数据出错");
				throw new BuzException("获取分页数据失败，" + (ex.InnerException != null ? ex.InnerException.Message : ex.Message));
			}
			return result;
		}
	}
}